package cn.com.ethos.search.query;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.UnsupportedEncodingException;
import java.net.Socket;

import org.apache.log4j.Logger;
import org.json.JSONException;

public class Worker implements Runnable {

	private ISearcher 	searcher;
	private Socket 		socket;

	private Logger logger = Logger.getLogger(this.getClass());
	
	public Worker(ISearcher searcher, Socket socket) {
		this.searcher   = searcher;
		this.socket 	= socket;
	}

	@Override
	public void run() {
		Response response = null;
		
		try{
			Request request = this.getRequest();
			logger.info("accept:"+this.socket.getInetAddress());
			logger.info("\tpage:" + request.getPage() + " size:" + request.getSize() + " query:"+request.getQuery());
			response = searcher.search(request);
		}catch(Exception ex) {
			logger.warn("Error occurred while searching,",ex);
			response = new ExceptionResponse(ex);
		}
		
		try {
			this.sendResponse(response);
		}catch(Exception ex) {
			logger.error("Writting message to output stream error:", ex);	
		} 
		
		try{
			this.socket.close();
		}catch(Exception ex) {
			logger.error("Closing socket error",ex);
		}		
	}

	private 
	void sendResponse(Response response)
			throws IOException {
		BufferedWriter writer = new BufferedWriter(new OutputStreamWriter (this.socket.getOutputStream(),"UTF-8"));
		writer.write(response.serialize());
		writer.close();
	}

	Request getRequest() 
			throws UnsupportedEncodingException,IOException,JSONException{
		
		BufferedReader br = new BufferedReader(new InputStreamReader(this.socket.getInputStream(),	"UTF-8"));
		String request = br.readLine();		
		return Request.parse(request);
	}

}
